<?php

namespace App\Library\Service;

use App\Library\Logic\KefuLogic;
use App\Library\Logic\MessageListLogic;
use App\Library\Requests\Base\IdRequest;
use App\Library\Requests\Kefu\KefuChangeStatusRequest;
use App\Library\Requests\Kefu\KefuPageRequest;
use App\Library\Requests\Kefu\KefuTurnRequest;
use Illuminate\Http\JsonResponse;

class KefuService extends BaseService
{
    /**
     * @param KefuLogic $logic
     */
    public function __construct(KefuLogic $logic)
    {
        $this->logic = $logic;
    }

    /**
     * status
     * @return JsonResponse
     */
    public function status(): JsonResponse
    {
        $k = 'kf:' . USERID;
        if (!cache()->has($k)) return fail(422);
        else return success(cache($k)['status']);
    }

    /**
     * paging
     * @param KefuPageRequest $request
     * @return JsonResponse
     */
    public function paging(KefuPageRequest $request): JsonResponse
    {
        $k = 'kf:' . USERID;
        return success($this->logic->paging($request, !cache()->has($k) ? USERID : cache($k)['sellerId']));
    }

    /**
     * changeStatus
     * @param KefuChangeStatusRequest $request
     * @return JsonResponse
     */
    public function changeStatus(KefuChangeStatusRequest $request): JsonResponse
    {
        $k = 'kf:' . USERID;
        if (!cache()->has($k)) return fail(422);
        else if ($this->logic->changeStatus($request->status)) {
            if ($request->status === 0) {
                foreach (redis('zrange', 'consult:' . USERID, 0, -1) as $v) cache()->forget('reception:' . $v);
                foreach (redis('keys', 'consultCount:' . USERID . ':*') as $val) cache()->forget($val);
                foreach (redis('keys', 'consultInfo:' . USERID . ':*') as $val) cache()->forget($val);
                cache()->forget('consult:' . USERID);
            }
            $cache = cache($k);
            $cache['status'] = $request->status;
            cache([$k => $cache]);
        }
        return success();
    }

    /**
     * 转接
     * @param KefuTurnRequest $request
     * @return JsonResponse
     */
    public function turn(KefuTurnRequest $request): JsonResponse
    {
        if ($request->kefuId === USERID) return fail(422);
        else if ($request->kefuId === $request->userId) return fail(422);
        else if ($request->userId === USERID) return fail(422);
        $k = 'kf:' . $request->kefuId;
        if (!cache()->has($k)) return failMessage('客服不存在');
        else if (cache($k)['status'] !== 1) return failMessage('客服不在线');
        $k = implode(':', ['reception', $request->userId]);
        if (!cache()->has($k)) {
            $lastInfo = MessageListLogic::lastInfo($request->userId);
            $score = now()->parse($lastInfo->created_at)->timestamp . now()->format('u');
            redis('zadd', 'consult:' . $request->kefuId, $score, $request->userId);
            cache([implode(':', ['consultInfo', $request->kefuId, $request->userId]) => $lastInfo->content]);
            cache([$k => $request->kefuId]);
            return success();
        }
        cache([$k => $request->kefuId]);
        $score = redis('zscore', 'consult:' . USERID, $request->userId);
        if ($score !== false) {
            redis('zrem', 'consult:' . USERID, $request->userId);
            redis('zadd', 'consult:' . $request->kefuId, $score, $request->userId);
        }
        $k = implode(':', ['consultCount', USERID, $request->userId]);
        $k1 = implode(':', ['consultCount', $request->kefuId, $request->userId]);
        if (cache()->has($k)) redis('renamenx', $k, $k1);
        $k = implode(':', ['consultInfo', USERID, $request->userId]);
        $k1 = implode(':', ['consultInfo', $request->kefuId, $request->userId]);
        if (cache()->has($k)) redis('renamenx', $k, $k1);
        return success();
    }

    /**
     * end
     * @param IdRequest $request
     * @return JsonResponse
     */
    public function end(IdRequest $request): JsonResponse
    {
        if (!cache()->has('kf:' . USERID)) return fail(422);
        $k = implode(':', ['reception', $request->id]);
        if (!cache()->has($k)) return success();
        if ((int)cache($k) !== USERID) return fail(422);
        cache()->forget($k);
        redis('zrem', 'consult:' . USERID, $request->id);
        cache()->forget(implode(':', ['consultCount', USERID, $request->id]));
        cache()->forget(implode(':', ['consultInfo', USERID, $request->id]));
        return success();
    }

    /**
     * consultList
     * @return JsonResponse
     */
    public function consultList(): JsonResponse
    {
        if (!cache()->has('kf:' . USERID)) return fail(422);
        $arr = [];
        foreach (redis('zrevrange', 'consult:' . USERID, 0, -1, true) as $k => $v) {
            $user = cache('user:' . $k);
            $arr[] = [
                'id' => $k,
                'mobile' => $user['mobile'],
                'nickname' => $user['nickname'],
                'avatar' => $user['avatar'],
                'timestamp' => now()->timestamp(intval($v / 1000000))->toDateTimeString(),
                'text' => cache(implode(':', ['consultInfo', USERID, $k])),
                'count' => (int)cache(implode(':', ['consultCount', USERID, $k])),
            ];
        }
        return success($arr);
    }
}
